package com.gwtjs.hbm2services;

import java.io.File;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;
import java.util.StringTokenizer;

/**
 * 生成dao的帮助工具 流操作应该提出来，参数的操作单独在此文件
 * 
 * @author aGuang
 * 
 */
public class ServiceHelper {

	private final String ANCHOR = "name";
	private final String QUOTE = "\"";
	private final String SPOT = ".";
	private final String DAO_PKG = "service";
	//private final String STAR = "*";
	// private final String SEMI = ";";
	private final String DAO_EXT = "Service.java";

	// private static int writeCount = 0; //写20次停止刷一下内存用

	private static ServiceHelper helper = new ServiceHelper();

	private ServiceHelper() {
	};

	public static ServiceHelper getInstance() {
		return helper;
	}

	/**
	 * 获取.hbm.xml文件转换成字符
	 * 
	 * @param fileName
	 * @return
	 */
	private String getFileData(String fileName) {
		FileReader in = null;
		try {
			File inputFile = new File(fileName);
			in = new FileReader(inputFile);
			char[] fileData = new char[(int) inputFile.length()];
			in.read(fileData);
			return String.copyValueOf(fileData);
		} catch (IOException e) {
			e.printStackTrace();
			return "读文件失败……";
		} finally {
			try {
				in.close();
			} catch (IOException e) {
				e.printStackTrace();
			}
		}
	}

	/**
	 * 获取DAO模板
	 * 
	 * @return
	 */
	private String getTemplateContent() {
		return this.getFileData(ServiceConfiger.getInstance().getTemplatePath());
	}

	/**
	 * 获取hbm的类全名
	 * 
	 * @param source
	 *            hbm.xml内容
	 * @return
	 */
	private String getHBM(String source) {
		int pos1 = source.indexOf(ANCHOR);
		int pos2 = source.indexOf(QUOTE, pos1);
		int pos3 = source.indexOf(QUOTE, pos2 + 1);

		return source.substring(pos2 + 1, pos3);
	}

	/**
	 * 获取dao的包名
	 * 
	 * @param pkg
	 * @return
	 */
	private String getPackageName(String pkg) {
		String rename = pkg.substring(0,
				pkg.lastIndexOf(SPOT, pkg.lastIndexOf(SPOT) - 1))
				+ SPOT + DAO_PKG;
		return rename;
	}

	/**
	 * 取导入的bean
	 * 
	 * @param hbm
	 * @return
	 */
	private String getImportName(String hbm) {
		return hbm.substring(0, hbm.lastIndexOf(SPOT)) ;
	}

	/**
	 * 取类名
	 * 
	 * @param pkg
	 * @return
	 */
	private String getClassName(String pkg) {
		String r = pkg.substring(pkg.lastIndexOf(SPOT) + 1, pkg.length());
		return r;
	}

	/**
	 * 取包的路径 将包转为路径
	 */
	private String getPathName(String pkg) {
		StringBuffer rePkg = new StringBuffer();
		String temp = this.getPackageName(pkg);
		// 用SPOT转换数据
		StringTokenizer token = new StringTokenizer(temp, SPOT);
		while (token.hasMoreTokens()) {
			rePkg.append(token.nextToken());
			rePkg.append("/");
		}
		return rePkg.toString();
	}

	/**
	 * 取Service文件全路径
	 * 
	 * @param hbm
	 * @return
	 */
	private String getServiceFileName(String hbm) {
		String r = this.getClassName(hbm) + DAO_EXT;
		return r;
	}

	/**
	 * 替换模板的内容
	 * 
	 * @param templateContent
	 * @param pkgData
	 * @param beans
	 * @param className
	 * @return
	 */
	private String doReplace(String templateContent, String pkgData,
			String beansPkg, String className) {
		String pkgTmp = "#PACKAGE#";
		String impBeanTmp = "#MODEL_PKG#";
		String classNameTmp = "#CLASSNAME#";
		templateContent = templateContent.replaceAll(pkgTmp, pkgData);
		templateContent = templateContent.replaceAll(impBeanTmp, beansPkg);
		templateContent = templateContent.replaceAll(classNameTmp, className);
		return templateContent;
	}

	/**
	 * 生成路径
	 * 
	 * @param filePath
	 *            文件路径
	 * @return
	 */
	private boolean mkdir(String filePath) {
		File dir = new File(filePath);
		return dir.mkdirs();
	}

	/**
	 * 写DAO文件
	 * 
	 * @param filePath
	 *            路径
	 * @param daoFileName
	 * @param fileContent
	 */
	private void bornFile(String filePath, String daoFileName,
			String fileContent) {
		this.mkdir(filePath);
		File outFile = new File(filePath + daoFileName);
		FileWriter out = null;
		try {
			out = new FileWriter(outFile);
			out.write(fileContent.toCharArray());
			// ++writeCount;
		} catch (IOException e) {
			System.out.println("写文件失败……");
			e.printStackTrace();
		} finally {
			try {
				out.close();
			} catch (IOException e) {
				e.printStackTrace();
			}
		}
	}

	/**
	 * 生成DaoImpl
	 * 
	 * @param templatePath
	 *            模板路径
	 * @param outputPath
	 *            输出路径
	 *            <p>
	 *            这个方法应该重构一下，把参数改成实体的属性，并把此方法上提到CodeGenerator里面
	 *            </p>
	 */
	public void generateService(String templatePath, String outputPath) {
		String hbmContent = this.getFileData(templatePath); // 取.hbm.xml内容
		String templateContent = this.getTemplateContent(); // 取模板内容 
		String pkgAllPath = this.getHBM(hbmContent); // 获取hbm的类全名

		String pkg = this.getPackageName(pkgAllPath); // 获取dao的包名
		String importData = this.getImportName(pkgAllPath); // 取导入的bean名称
		System.out.println(importData);
		String className = this.getClassName(pkgAllPath); // 取类名
		String filePath = this.getPathName(pkgAllPath); // 获取输出全路径
		String fileName = this.getServiceFileName(pkgAllPath);// dao类的名字
		String content = this.doReplace(templateContent, pkg, importData,
				className);

		this.bornFile(outputPath + "\\" + filePath, fileName, content);
	}
}
